package com.wkbb.basic.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.wkbb.basic.config.BasicConfig;
import com.wkbb.basic.feign.DoorFeignService;
import com.wkbb.basic.feign.TcCloudFeignService;
import com.wkbb.basic.feign.WxFeignService;
import com.wkbb.basic.mapper.UserMapper;
import com.wkbb.basic.mapper.YoutuFaceMapper;
import com.wkbb.basic.mapper.YoutuPersonMapper;
import com.wkbb.basic.model.*;
import com.wkbb.basic.service.*;
import com.wkbb.basic.thread.*;
import com.wkbb.basic.utils.*;
import com.wkbb.common.base.BaseServiceImpl;
import com.wkbb.common.config.ServiceConfig;
import com.wkbb.common.constants.Constants;
import com.wkbb.common.constants.ErrorCode;
import com.wkbb.common.constants.RedisKeyConstant;
import com.wkbb.common.dto.ResultDTO;
import com.wkbb.common.dto.im.COSCredentialDto;
import com.wkbb.common.dto.wx.AccountDto;
import com.wkbb.common.enums.*;
import com.wkbb.common.redis.RedisTemplateUtil;
import com.wkbb.common.utils.StringUtil;
import com.wkbb.common.utils.ThreadPoolUtil;
import com.wkbb.common.utils.UuIdUtil;
//import com.wkbb.common.vo.DeviceUserFaceVo;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.*;
import java.util.concurrent.TimeUnit;

/**
 * @author dengjingyuan
 * @date 2019-07-29 10:58
 */
@Service
@Slf4j
public class YouTuServiceImpl extends BaseServiceImpl<YoutuPerson> implements YouTuService {

    @Autowired
    private BasicConfig basicConfig;
    @Autowired
    private ServiceConfig serviceConfig;
    @Autowired
    private YoutuPersonMapper youtuPersonMapper;
    @Autowired
    private YoutuFaceMapper youtuFaceMapper;
    @Autowired
    private TcCloudFeignService tcCloudFeignService;
    @Autowired
    private RedisTemplateUtil redisTemplateUtil;
    @Autowired
    private DeviceBoxService deviceBoxService;
    @Autowired
    @Lazy
    private XmppService xmppService;
    @Autowired
    private WxFeignService wxFeignService;
    @Autowired
    private UserService userService;

    @Autowired
    private UserMapper userMapper;

    @Autowired
    private UserFacePersonConfigService userFacePersonConfigService;

    @Autowired
    private YouTuService youTuService;

    @Autowired
    private WebankService webankService;

    @Autowired
    private OrganizationService organizationService;

    @Autowired
    private DoorFeignService doorFeignService;

    @Autowired
    private WebankUtilService webankUtilService;

    @Autowired
    private OrganizationWebankService organizationWebankService;
    
    @Override
    public String geYouTuSign() {
        try {
            String sign = YouTuSign.getSign("0", basicConfig.getUtuSdkAppid().toString(), basicConfig.getUtuSecretId(), basicConfig.getUtuSecretKey());
            log.info("生成优图sign-{}", sign);
            return sign;
        } catch (Exception e) {
            e.printStackTrace();
            log.error("生成优图sign失败");
        }
        return null;
    }

    @Override
    public String addPerson(Long orgId, String personId, ImageOfbase64UtilDto imageOfbase64UtilDto, Long accountId, Long userId) {
        String result = null;

        JSONObject jsonObject = new JSONObject();

        try {

            log.info("--------开始注册优图个体--------" + getAddUserFaceLog(userId, orgId));
            long startTime = System.currentTimeMillis();
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            //group_ids进行补位
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));

            long encodeImageToBase64_startTime = System.currentTimeMillis();
//            String image = FileUtil.encodeImageToBase64(new URL(picUrl));
            long encodeImageToBase64_endTime = System.currentTimeMillis();

            jsonObject.put("group_ids", accountList);
            jsonObject.put("person_id", personId);
            jsonObject.put("image", imageOfbase64UtilDto.getBase64());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.ADDPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("*****YouTuServiceImpl******总耗时:{},encodeImageToBase64【耗时:{}，url:{}】", System.currentTimeMillis() - startTime, encodeImageToBase64_endTime - encodeImageToBase64_startTime, imageOfbase64UtilDto.getImageUrl());

            log.info("--------注册优图个体结束--------" + getAddUserFaceLog(userId, orgId));
            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                JSONObject jsonObject1 = JSONObject.parseObject(result);
                String faceId = jsonObject1.get("face_id").toString();

                CheckYouTuFace(personId, true, faceId);


            }
        } catch (Exception e) {
            //同时删除微众人脸
            CheckYouTuFace(personId, false, null);
            log.error("----------个体创建失败----------e:{}", e.getMessage());
        }

        return result;
    }

    @Override
    public String deletePerson(Long orgId, Long userId) {

        YoutuPerson youtuPerson = getYoutuPerson(orgId, userId);
        log.info("----------查询对应的youtuPerson------youtuPerso:{}", youtuPerson);


        String result = null;
        JSONObject jsonObject = new JSONObject();

        log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
        OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);
        log.info("--------获取学校微众appid结束--------orgId:{}", orgId);

        if (null == organizationWebank) {
            log.info("--------此学校没有绑定微众appid--------orgId:{}", orgId);
            return null;
        }
        try {
            //在微众删除相应人员
            String webankResult = webankUtilService.delPerson(youtuPerson.getPersonId(), false, organizationWebank.getWebankAppid(), organizationWebank.getWebankSecret(), orgId);
            //删除微众人脸的时候，若用户不存在，不予理会，不妨碍优图逻辑
            if ((!WebankUtil.userNotExists(webankResult))) {
                //微众人脸删除失败，抛出异常终止人脸删除
                if (!WebankUtil.checkIfSuccess(webankResult)) {
                    log.error("删除微众人员失败:{}", webankResult);
                    return WebankUtil.getMessage(webankResult);
                }
            }

            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            //group_ids进行补位
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
            jsonObject.put("group_ids", accountList);
            jsonObject.put("person_id", youtuPerson.getPersonId());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                Map<String, Object> params = new HashMap<>(1);
                params.put("personId", youtuPerson.getPersonId());
                if (null != youtuPerson) {
                    //在巨龙盒子删除相应人员
                    deviceBoxService.deleteBoxPerson(youtuPerson.getPersonId(), orgId);

                    youtuPerson.setPersonId(youtuPerson.getPersonId());
                    youtuPerson.setStatus(false);
                    youtuPersonMapper.update(youtuPerson);

                    List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);
                    if (null != youtuFaceList && youtuFaceList.size() > 0) {
                        for (YoutuFace youtuFace : youtuFaceList) {
                            youtuFace.setYouTuStatus(false);
                            youtuFace.setPersonId(youtuPerson.getPersonId());
                            youtuFaceMapper.update(youtuFace);

                            //通过userCode获取用户信息
                            Map<String, Object> param = new HashMap<>(1);
                            param.put("userCode", youtuPerson.getPersonId());

                            User user = userService.getByMapParams(param);

                            if (null != user) {

                                ThreadPoolUtil.addPoolTask(new SynUserAccessXmppTask(doorFeignService, orgId, user.getId(), RoleTypeEnum.FAMILY, xmppService, null, null, null, true, false, false, false,null,null));

                            }
                        }
                    }
                }
            }
            log.info("个体删除成功JsonObject-{}", jsonObject);
        } catch (Exception e) {
            System.out.println(e);
            log.info("个体删除失败JsonObject-{}", jsonObject);
        }
        return result;
    }

    @Override
    public String addFace(List<ImageOfbase64UtilDto> imagesList, String personId, Long orgId, Long userId, Integer type, Short similar) {

        String result = null;
        JSONObject jsonObject = new JSONObject();
        //获取签名

        log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
        OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);
        log.info("--------获取学校微众appid结束--------orgId:{}", orgId);

        if (null == organizationWebank) {
            log.info("--------此学校没有绑定微众appid--------orgId:{}", orgId);
            return null;
        }

        try {
            Map<String, Object> newParam = new HashMap<>(2);
            newParam.put("userId", userId);
            newParam.put("orgId", orgId);
            YoutuPerson youTuPerson = youtuPersonMapper.getByMapParams(newParam);

            if (null != youTuPerson) {
                //查询数据库,如果有人脸,删除以前的人脸,再添加人脸
                deleteFace(personId, orgId);

                webankService.addWebankPerson(youTuPerson.getAccountId(), userId, orgId, personId, imagesList.get(0).getImageUrl(), type, similar);

                List base64List = new ArrayList();
                List picUrlList = new ArrayList();
                for (ImageOfbase64UtilDto imageOfbase64UtilDto : imagesList) {
                    base64List.add(imageOfbase64UtilDto.getBase64());
                    picUrlList.add(imageOfbase64UtilDto.getImageUrl());

                    addPerson(orgId, personId, imageOfbase64UtilDto, youTuPerson.getAccountId(), userId);
                }
                log.info("--------优图个体绑定人脸结束--------" + getAddUserFaceLog(userId, orgId));
            }
        } catch (Exception e) {
            e.getMessage();
            log.info("人脸添加失败");
        }

        return result;
    }


    @Override
    public String deleteFace(String personId, Long orgId) {


        //查询数据库,如果有人脸,删除以前的人脸,再添加人脸
        Map<String, Object> params = new HashMap<>(1);
        params.put("personId", personId);
        YoutuFace newYouTuFace = youtuFaceMapper.getByMapParams(params);

        String result = null;
        List faceIdList = null;
        if (null != newYouTuFace) {
            JSONObject jsonObject = new JSONObject();

            log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
            OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);

            if (null == organizationWebank) {
                log.info("--------此学校没有绑定微众appid--------orgId:{}", orgId);
                return null;
            }
            log.info("--------获取学校微众appid结束--------orgId:{}", orgId);
            try {
                //获取签名
                String sign = geYouTuSign();
                jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
                jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
                jsonObject.put("person_id", personId);

                if (basicConfig.getUtuFlag()==null?false:basicConfig.getUtuFlag()&& StringUtil.isNotEmptyIgnoreBlank(newYouTuFace.getFaceId())) {

                    faceIdList = Arrays.asList(newYouTuFace.getFaceId().split(Constants.SEPARATOR_MARK));
                    jsonObject.put("face_ids", faceIdList);
                    result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEFACE, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
                }

                log.info("人脸删除成功JsonObject-{}", jsonObject);

            } catch (Exception e) {
                e.getMessage();
                log.info("人脸删除失败JsonObject-{}", jsonObject);
            }
        }
        return result;
    }

    @Override
    public void deleteYouTuFace(String personId) {
        Map<String, Object> newParam = new HashMap<>(2);
        newParam.put("personId", personId);
        YoutuFace youtuFace = youtuFaceMapper.getByMapParams(newParam);
        if (null != youtuFace) {
            youtuFace.setYouTuStatus(false);
            youtuFace.setWebankStatus(false);
            youtuFaceMapper.update(youtuFace);
            YoutuPerson youtuPerson = webankService.getYoutuPersonByParam(personId);

            if (null != youtuPerson) {
                youtuPerson.setStatus(false);
                youtuPersonMapper.update(youtuPerson);
            }
        }
    }

    @Override
    public void updateYouTuFace(Long userId,Long orgId, String personId,String url,Integer type, Short similar) {
        Map<String, Object> newParam = new HashMap<>(2);
        newParam.put("personId", personId);
        YoutuFace youtuFace = youtuFaceMapper.getByMapParams(newParam);
        if (null != youtuFace) {
            youtuFace.setWebUrl(url);
            youtuFaceMapper.update(youtuFace);
        }
        //处理人脸配置
        webankService.checkPersonConfig( userId,  orgId,  type,  similar,  personId);
    }

    @Override
    public String getPersons(Long orgId) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            String groupIds = UuIdUtil.getGroupIds(ProfilesActiveEnum.TEST.getDesc(), orgId.toString());
            jsonObject.put("group_id", groupIds);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.PULLPERSONS, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

            log.info("拉取个体成功JsonObject-{}", jsonObject);
        } catch (Exception e) {
            e.getMessage();
            log.info("拉取个体失败JsonObject-{}", jsonObject);
        }
        return result;
    }

    @Override
    public String getPullFaces(String personId) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            jsonObject.put("person_id", personId);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.PULLFACES, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("拉取人脸成功JsonObject-{}", jsonObject);
        } catch (Exception e) {
            e.getMessage();
            log.info("拉取人脸失败JsonObject-{}", jsonObject);
        }
        return result;
    }

    @Override
    public String getFaceIdentify(Long orgId, ImageOfbase64UtilDto imageOfbase64UtilDto) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            jsonObject.put("group_ids", accountList);
            jsonObject.put("image", imageOfbase64UtilDto.getBase64());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.FACEIDENTIFY, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("人脸识别成功result-{}", result);
        } catch (Exception e) {
            e.getMessage();
            log.info("人脸识别失败result-{}", result);
        }
        return result;
    }

    @Override
    public String getFaceIdentifyResult(Long orgId, ImageOfbase64UtilDto imageOfbase64UtilDto) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
//            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            jsonObject.put("group_id", groupIds);
            jsonObject.put("image", imageOfbase64UtilDto.getBase64());
            jsonObject.put("topn", 1);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.FACEIDENTIFY, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("人脸识别成功result-{}", result);
        } catch (Exception e) {
            e.getMessage();
            log.info("人脸识别失败result-{}", result);
        }
        return result;
    }

    @Override
    public String getFaceDetect(ImageOfbase64UtilDto imageOfbase64UtilDto) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
//            jsonObject.put("image", FileUtil.encodeImageToBase64(new URL(picUrl)));
            //改成直接传base64结果进来，减少多个地方对同一张图片编码
            jsonObject.put("image", imageOfbase64UtilDto.getBase64());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.FACEDETECT, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("人脸检测result-{}", result);
        } catch (Exception e) {
            e.getMessage();
            log.info("人脸检测失败result-{}", result);
        }
        return result;
    }

    @Override
    public String getFaceCompare(ImageOfbase64UtilDto imageOfBase64_a, ImageOfbase64UtilDto imageOfBase64_b) {
        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            jsonObject.put("image_a", imageOfBase64_a.getBase64());
            jsonObject.put("image_b", imageOfBase64_b.getBase64());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.FACECOMPARE, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            log.info("人脸对比result-{}", result);
        } catch (Exception e) {
            e.getMessage();
            log.info("人脸对比失败result-{}", result);
        }
        return result;
    }

    @Override
    public String addUserFace(ImageOfbase64UtilDto imageOfbase64UtilDto_a, String userCode, Long orgId, Long accountId, Long userId) {

        log.info("\n获取用户信息............ 开始..准备开始获取分布式锁......" + getAddUserFaceLog(userId, orgId), userId);
        boolean lock = false;

        String result = null;
        int retryCount = 0;
        while (!lock) {


            try {
                lock = redisTemplateUtil.tryLock(getAddUserFaceRedisKey(userId, orgId), userId.toString(), 120, TimeUnit.SECONDS);
                log.info("#################" + getAddUserFaceLog(userId, orgId), "加锁 ", userId.toString());

            } catch (Exception e) {
                log.info("#################加锁失败..等待锁过期 ：" + getAddUserFaceLog(userId, orgId), userId);
                e.printStackTrace();

            }

            if (lock) {//加锁成功

                log.info("----------获取当前线程名称----------ThreadName:{}" + getAddUserFaceLog(userId, orgId), userId, Thread.currentThread().getName());

                //判断当前用户在当前学校是否有注册人脸,如果没有人脸就注册person并且注册人脸,如果有一张就注册2张,如果有2张就不注册了
                log.info("---------准备注册人脸的学校ID和用户ID----------orgId:{},userId:{}", orgId, userId);


                //通过userCode获取个体是否创建
                YoutuPerson youtuPerson = getYoutuPerson(orgId, userId);

//                Boolean flag = true;没用上
                if (null == youtuPerson) {
                    //创建个体
                    log.info("----------开始创建个体---------}");

                    //生成userCode
                    userCode = UuIdUtil.getUserCodeByUUId();
                    log.info("--------创建个体最新生成的userCode---------,userCode:{}", userCode);

                    //result = addPerson(orgId, userCode, imageOfbase64UtilDto_a, accountId, userId);

                    log.info("----------创建个体结束----------{}", result);
//                    flag = false;

                    //微众注册人员失败的话返回一个不是json的str
//                    if (!JSON.isValid(result)) {//始终为true

                        releaseLockAddUserFace(orgId, userId);
                        return result;
//                    }


                } else {
                    userCode = youtuPerson.getPersonId();

                }

                //如果当前用户有2张人脸,不会新增
                log.info("----------当前用户有个体,准备获取已有人脸数---------" + getAddUserFaceLog(userId, orgId));
                List<YoutuFace> youTuFaceList = selectFaceByuserCode(userId, orgId);

                log.info("----------获取已有人脸数第一次检测---------youTuFaceList:{}", youTuFaceList.size());

                log.info("----------获取已有人脸数第一次检测--------" + getAddUserFaceLog(userId, orgId) + ",youTuFaceList:{}", youTuFaceList.size());


                log.info("---------打印人脸注册结果----------result:{}", result);
                try {
                    releaseLockAddUserFace(orgId, userId);
                } catch (Exception e) {
                    log.info("#################释放锁失败..等待锁过期 ," + getAddUserFaceLog(userId, orgId), userId);
                    e.printStackTrace();
                }
            } else {
                try {
                    retryCount++;
                    if(retryCount>20){
                        log.info("加锁失败，重试超过20次，新增人脸失败...orgId:{}" ,  orgId);
                        break;
                    }
                    log.info("等待500ms重试..." + getAddUserFaceLog(userId, orgId), userId);
                    Thread.sleep(500L);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }

        return result;
    }

    @Override
    public void releaseLockAddUserFace(Long orgId, Long userId) {
        log.info("#################" + getAddUserFaceLog(userId, orgId), "开始释放锁 ", userId);

        redisTemplateUtil.releaseLock(getAddUserFaceRedisKey(userId, orgId), userId.toString());

        log.info("#################" + getAddUserFaceLog(userId, orgId), "释放锁成功 ", userId);
    }

    @Override
    public String getAddUserFaceLog(Long userId, Long orgId) {
        return RedisKeyConstant.WKBB_BASIC + "addUserFace:" + "orgId:" + orgId + ":" + "userId:" + userId + ":{}";
    }

    public String getFaceLog(Long userId, Long orgId) {
        return RedisKeyConstant.WKBB_BASIC + "userFace:" + "orgId:" + orgId + ":" + "userId:" + userId + ":{}";
    }

    @Override
    public String getAddUserFaceRedisKey(Long userId, Long orgId) {
        return RedisKeyConstant.WKBB_BASIC + "addUserFace:" + "orgId_" + orgId + ":" + "userId_" + userId;
    }

    public String getFaceRedisKey(Long userId, Long orgId) {
        return RedisKeyConstant.WKBB_BASIC + "userFace:" + "orgId_" + orgId + ":" + "userId_" + userId;
    }

    @Override
    public YoutuPerson getYoutuPerson(Long orgId, Long userId) {
        Map<String, Object> params = new HashMap<>(3);
        params.put("orgId", orgId);
        params.put("userId", userId);

        return youtuPersonMapper.getByMapParams(params);
    }

    @Override
    public List<YoutuFace> selectFaceByuserCode(Long userId, Long orgId) {
        HashMap<String, Object> params = new HashMap<>(2);
        params.put("userId", userId);
        params.put("orgId", orgId);

        return youtuFaceMapper.getListFaceByMapParams(params);
    }

    @Override
    public String getSmsCode(String mobile) {
        log.info("*************发送人脸短信验证码*************}", mobile);
        tcCloudFeignService.sendCloudSmsByTemId(mobile, SmsTypeEnum.FACESMSCODE.getValue());

        String key = getSmsCodeRedisKey(mobile, SmsTypeEnum.FACESMSCODE.getValue());
        String verifyCode = (String) redisTemplateUtil.get(key);
        if (null == verifyCode) {
            return ErrorCode.FACESMSCODEERROR.getMessage();
        }
        return verifyCode;
    }

    public String getSmsCodeRedisKey(String mobile, Integer type) {
        return RedisKeyConstant.WKBB_TC_SMS_VERIFY + "type:" + type + ":mobile:" + mobile;
    }


    @Override
    public String importUserFace(String picUrl, String personId, Long orgId, Long accountId, Long userId, Boolean flag) {

        String result = null;
        log.info("---------准备注册人脸的学校ID和用户ID----------orgId:{},userId:{}", orgId, userId);
        YoutuPerson youtuPerson = getYoutuPerson(Long.parseLong(String.valueOf(orgId)), userId);

        if (null == youtuPerson) {
            List<ImageOfbase64UtilDto> imageOfbase64UtilDtoList = FileUtil.batchEncodeImageToBase64(changeUrl(picUrl));
            //    result = addUserFace(imageOfbase64UtilDtoList.isEmpty()?null:imageOfbase64UtilDtoList.get(0), null, UuIdUtil.getUserCodeByUUId(), Long.parseLong(String.valueOf(orgId)), accountId, userId);

            log.info("---------注册完成personId----------orgId:{},userId:{}", orgId, userId);

            youtuPerson = getYoutuPerson(Long.parseLong(String.valueOf(orgId)), userId);

            if (null != youtuPerson) {
                Map<String, Object> params = new HashMap<>(2);
                params.put("personId", youtuPerson.getPersonId());
                List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);

                for (YoutuFace youtuFace : youtuFaceList) {
                    youtuFace.setDevicePath(picUrl);
                    youtuFaceMapper.update(youtuFace);
                }
            }

        } else {
            Map<String, Object> params = new HashMap<>(2);
            params.put("personId", youtuPerson.getPersonId());
            List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);

            if (youtuFaceList.size() == 1) {
                List<ImageOfbase64UtilDto> imageOfbase64UtilDtoList = FileUtil.batchEncodeImageToBase64(youtuFaceList.get(0).getWebUrl() + Constants.SEPARATOR_MARK + changeUrl(picUrl));

                //  result = addUserFace(imageOfbase64UtilDtoList.isEmpty()?null:imageOfbase64UtilDtoList.get(0), imageOfbase64UtilDtoList.size()<2?null:imageOfbase64UtilDtoList.get(1), youtuPerson.getPersonId(), Long.parseLong(String.valueOf(orgId)), accountId, userId);

                youtuFaceList = youtuFaceMapper.getListByMapParams(params);

                for (YoutuFace youtuFace : youtuFaceList) {
                    if (null == youtuFace.getDevicePath()) {
                        youtuFace.setDevicePath(picUrl);
                        youtuFaceMapper.update(youtuFace);
                    }
                }
            }

        }

        return result;
    }


    @Override
    public ArrayList<Object> deletePersonByOrgId(Long orgId) {
        Map<String, Object> params = new HashMap<>(2);
        params.put("orgId", orgId);
        List<YoutuPerson> youtuPersonList = youtuPersonMapper.getListByMapParams(params);

        ArrayList<Object> objects = new ArrayList<>();
        JSONObject json = new JSONObject();

        if (null != youtuPersonList && youtuPersonList.size() > 0) {
            for (YoutuPerson youtuPerson : youtuPersonList) {

                String result = null;
                JSONObject jsonObject = new JSONObject();
                try {

                    //获取签名
                    String sign = geYouTuSign();
                    jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
                    jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
                    //group_ids进行补位
                    String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
                    List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
                    jsonObject.put("group_ids", accountList);
                    jsonObject.put("person_id", youtuPerson.getPersonId());
                    result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

                    log.info("个体删除成功JsonObject-{}", jsonObject);
                } catch (Exception e) {
                    System.out.println(e);
                    log.info("个体删除失败JsonObject-{}", jsonObject);
                }
            }
        }
        return objects;
    }

    /**
     * 检查是否上传了人脸接口
     *
     * @param userId
     */
    @Override
    public Boolean checkHasUploadFace(Long orgId, Long userId) {
        Boolean hasUploadFace = false;
        //查询
        User user = userMapper.getByPrimaryKey(userId);
        //在这里去查询人脸的图片信息,如果能查询到,说明已经上传了人脸
        if (null != user) {
            Map<String, Object> paramsMap = new HashMap<>(2);
            paramsMap.put("orgId", orgId);
            paramsMap.put("userId", userId);
            List<YoutuPerson> userFaceList = youtuPersonMapper.getListByMapParams(paramsMap);

            if (CollectionUtils.isNotEmpty(userFaceList)) {
                hasUploadFace = true;
            }
        }
        return hasUploadFace;
    }

    @Override
    @Transactional
    public String saveUserFace(ImageOfbase64UtilDto imageOfbase64UtilDto_a, String userCode, Long orgId, Long accountId, Long userId, Short similar) throws Exception {
        boolean lock = false;
        String result = "";
        int retryCount = 0;
        String lockKey = getFaceRedisKey(userId, orgId);
        while (!lock) {
            try {
                lock = redisTemplateUtil.tryLock(lockKey, userId.toString(), 120, TimeUnit.SECONDS);
                log.info("#################" + getFaceLog(userId, orgId), "加锁 ", userId.toString());
            } catch (Exception e) {
                log.info("#################加锁失败..等待锁过期 ：" + getFaceLog(userId, orgId), userId);
                e.printStackTrace();
            }
            if (lock) {
                log.info("----------获取当前线程名称----------ThreadName:{}" + getAddUserFaceLog(userId, orgId), userId, Thread.currentThread().getName());

                try {
                    List<YoutuFace> userFaceList = selectFaceByuserCode(userId, orgId);
                    log.info("----saveUserFace----userFaceList={}", JSONObject.toJSONString(userFaceList));
                    Map<String, Object> faceMap = new HashMap<>();
                    if (CollectionUtils.isNotEmpty(userFaceList)) {
                        userCode = userFaceList.get(0).getPersonId();

                        for (YoutuFace youtuFace : userFaceList) {
                            String webUrl = youtuFace.getWebUrl();
                            if (!faceMap.containsKey(webUrl)) {
                                faceMap.put(webUrl, youtuFace);
                            }
                        }
                    }
                    //判断上传的两张照片是否是之前的,如果不是,则直接替换,如果是,则不做任何修改,如果只替换了一张?那就新增一张?还是替换一张?
                    //如果picUrla不为空,picUrlb为空,则说明是变更图片,需要把之前的图片先删除
                    //人脸ID集合(以;进行分割)
                    log.info("----saveUserFace----faceMap={}", JSONObject.toJSONString(faceMap));
                    List<String> faceIds = new ArrayList<>();
                    if (!faceMap.isEmpty()) {
                        if (StringUtil.isNotEmpty(imageOfbase64UtilDto_a.getImageUrl())) {
                            //计算出faceIds
                            if (faceMap.size() == 1) {
                                YoutuFace youtuFace = (YoutuFace) faceMap.get(imageOfbase64UtilDto_a.getImageUrl());
                                if (null == youtuFace) {
                                    //不存在,说明是变更,先删除之前的照片,再上传
                                    YoutuFace face = (YoutuFace) faceMap.get(0);
                                    String faceId = face.getFaceId();
                                    log.info("----saveUserFace----单个照片替换faceId={}", faceId);
                                    deleteFace(youtuFace.getPersonId(), orgId);
                                }
                            }
                        }

                    }
                    //先删除,再新增
                    if (CollectionUtils.isNotEmpty(faceIds)) {
                        Map<String, Object> paramsMap = new HashMap<>(2);
                        paramsMap.put("faceId", faceIds);
                        YoutuFace youtuFace = youtuFaceMapper.getByMapParams(paramsMap);

                        if (null != youtuFace) {

                            deleteFace(youtuFace.getPersonId(), orgId);
                        }
                    }
                    //result = addUserFace(imageOfbase64UtilDto_a, imageOfbase64UtilDto_b, userCode, orgId, accountId, userId);

                    YoutuPerson youtuPerson = getYoutuPerson(orgId, userId);

                    if (null != youtuPerson) {
                        //增加或者update配置表
                        webankService.saveUserFacePersonConfig( userId,  orgId,  similar, youtuPerson.getPersonId());
                    }
                } catch (Exception e) {
                    log.error("-----------出错了--------", e);
                    log.info("----------获取当前线程名称----------ThreadName:{}" + getAddUserFaceLog(userId, orgId), userId, Thread.currentThread().getName());
                } finally {
                    log.info("-----------释放锁开始--------");
                    log.info("----------获取当前线程名称----------ThreadName:{}" + getAddUserFaceLog(userId, orgId), userId, Thread.currentThread().getName());
                    redisTemplateUtil.releaseLock(lockKey, userId.toString());
                    log.info("-----------释放锁结束--------lock={}", lock);
                }
            } else {
                try {
                    retryCount++;
                    if(retryCount>20){
                        log.info("加锁失败，重试超过20次，保存人脸失败...:{}" ,  getFaceLog(userId, orgId));
                        break;
                    }
                    log.info("等待500ms重试..." + getFaceLog(userId, orgId), userId);
                    Thread.sleep(500L);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
        return result;
    }

    //计算将要被删除的faceIdList
    private List<String> getFaceIdList(Map<String, Object> faceMap, YoutuFace newYoutuFace) {
        List<String> faceIds = new ArrayList<>();
        for (Map.Entry<String, Object> map : faceMap.entrySet()) {
            System.out.println("key:" + map.getKey() + " value:" + map.getValue());
            YoutuFace youtuFace = (YoutuFace) map.getValue();
            if (youtuFace != newYoutuFace) {
                faceIds.add(youtuFace.getFaceId());
            }
        }
        log.info("----getFaceIdList----faceIds={}", faceIds);
        return faceIds;
    }

    @Override
    public ArrayList<Object> deletePersonByAccountId(Long accountId) {
        Map<String, Object> params = new HashMap<>(2);
        params.put("accountId", accountId);
        List<YoutuPerson> youtuPersonList = youtuPersonMapper.getListByMapParams(params);

        ArrayList<Object> objects = new ArrayList<>();
        JSONObject json = new JSONObject();

        if (null != youtuPersonList && youtuPersonList.size() > 0) {
            for (YoutuPerson youtuPerson : youtuPersonList) {

                String result = deletePersonByAccountId(accountId, youtuPerson.getPersonId(), youtuPerson.getOrgId());

                if (!JSON.isValid(result) || !YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                    json.put("personId", youtuPerson.getPersonId());
                    json.put("errormsg", StringUtil.isEmpty(result) ? "failure" : result);
                    objects.add(json);
                }
            }
        }
        return objects;
    }

    public String deletePersonByAccountId(Long accountId, String personId, Long orgId) {

        log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
        OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);
        log.info("--------获取学校微众appid结束--------orgId:{}", orgId);

        if (null == organizationWebank) {
            log.info("--------此学校没有绑定微众appid--------orgId:{}", orgId);
            return null;
        }

        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //在微众删除相应人员
            String webankResult = webankUtilService.delPerson(personId, false, organizationWebank.getWebankAppid(), organizationWebank.getWebankSecret(), orgId);
            //删除微众人脸的时候，若用户不存在，不予理会，不妨碍优图逻辑
            if ((!WebankUtil.userNotExists(webankResult))) {
                //微众人脸删除失败，抛出异常终止人脸删除
                if (!WebankUtil.checkIfSuccess(webankResult)) {
                    log.error("删除微众人员失败:{}", webankResult);
                    return WebankUtil.getMessage(webankResult);
                }
            }

            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            //group_ids进行补位
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), accountId.toString());
            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
            jsonObject.put("group_ids", accountList);
            jsonObject.put("person_id", personId);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                Map<String, Object> params = new HashMap<>(2);
                params.put("personId", personId);
                YoutuPerson youtuPerson = webankService.getYoutuPersonByParam(personId);
                if (null != youtuPerson) {
                    //在巨龙盒子删除相应人员
                    deviceBoxService.deleteBoxPerson(personId, orgId);

                    youtuPerson.setPersonId(personId);
                    youtuPerson.setStatus(false);
                    youtuPersonMapper.update(youtuPerson);

                    List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);
                    if (null != youtuFaceList && youtuFaceList.size() > 0) {
                        for (YoutuFace youtuFace : youtuFaceList) {
                            youtuFace.setYouTuStatus(false);
                            youtuFace.setPersonId(personId);
                            youtuFaceMapper.update(youtuFace);

                            //通过userCode获取用户信息
                            Map<String, Object> param = new HashMap<>(1);
                            param.put("userCode", personId);

                            User user = userService.getByMapParams(param);

                            if (null != user) {
                                //通过accountId查询orgId
                                ResultDTO<AccountDto> account = wxFeignService.getAccount(accountId);
                                if (ResultDTO.checkSuccess(account) && account.getData() != null && null != account.getData().getOrgInfo()) {

                                    JSONArray orgInfoList = JSONObject.parseArray(JSONObject.toJSONString(account.getData().getOrgInfo()));

                                    for (int i = 0; i < orgInfoList.size(); i++) {
                                        JSONObject orgInfoObject = JSONObject.parseObject(orgInfoList.get(i).toString());
                                        Long orgIdList = Long.parseLong(orgInfoObject.get("orgId").toString());
                                        //同步信息到xmpp
                                        ThreadPoolUtil.addPoolTask(new SynUserAccessXmppTask(doorFeignService, orgIdList, user.getId(), RoleTypeEnum.FAMILY, xmppService, null, null, null, true, false, false, false,null,null));
                                    }
                                }
                            }
                        }
                    }
                }
            }
            log.info("个体删除成功JsonObject-{}", jsonObject);
        } catch (Exception e) {
            System.out.println(e);
            log.info("个体删除失败JsonObject-{}", jsonObject);
        }
        return result;
    }

    @Override
    public void repairYouTuInfo() {
        try {
            log.info("---------准备修复优图数据----------");
            HashMap<String, Object> params = new HashMap<>(2);
            params.put("status", 0);
            List<YoutuFace> YoutuFaceList = youtuFaceMapper.getListFaceByStatus(params);


            if (YoutuFaceList.isEmpty()) {
                log.info("---------没查询到需要修复的数据----------");
                return;
            }

            log.info("---------统计本次所有需要修复的数据量----------YoutuFaceList:{}", YoutuFaceList.size());

            int size = YoutuFaceList.size();

            for (YoutuFace youtuFace : YoutuFaceList) {

                log.info("---------还剩下多少数据量未执行----------YoutuFaceList:{}", --size);
                String faceUrl = changeUrl(youtuFace.getWebUrl());
                params.put("status", 0);
                params.put("personId", youtuFace.getPersonId());
                log.info("---------获取当前用户personId----------personId:{}", youtuFace.getPersonId());

                List<YoutuPerson> youtuPersonList = youtuPersonMapper.getPersonByStatus(params);

                if (!youtuPersonList.isEmpty()) {

                    User user = userMapper.getByPrimaryKey(youtuPersonList.get(0).getUserId());
                    if (user != null) {
                        List<LinkedHashMap<String, Object>> roleTypeJsonDto = (List<LinkedHashMap<String, Object>>) user.getRoleType();
                        List<Object> orgList = new ArrayList<>();
                        for (LinkedHashMap<String, Object> map : roleTypeJsonDto) {
                            if (null != map.get("orgId")) {
                                orgList.add(map.get("orgId"));
                            }
                        }
                        //将用户的人脸关联上用户所在的所有的组
                        log.info("---------获取当前用户所在学校----------orgList:{}", orgList);
                        if (null != orgList && orgList.size() > 0) {
                            for (Object orgId : orgList) {

                                log.info("----------需要修复的用户ID----------userId:{}", youtuPersonList.get(0).getUserId());
                                BasicRepairAddUserFaceTask basicRepairAddUserFaceTask = new BasicRepairAddUserFaceTask(youTuService, faceUrl, youtuPersonList, orgId);
                                ThreadPoolUtil.addTask(basicRepairAddUserFaceTask);

                            }
                        } else {
                            log.info("----------此用户是游客----------userId:{}", youtuPersonList.get(0).getUserId());
                        }
                    } else {
                        log.info("----------找不到对应用户----------userId:{}", youtuPersonList.get(0).getUserId());
                    }
                } else {
                    log.info("----------找不到对应的personId----------personId:{}", youtuFace.getPersonId());
                }
            }
        } catch (Exception e) {
            log.info("---------修复接口失败----------", e);
        }
    }


    @Override
    public void repairAddUserFaceAsyn(ImageOfbase64UtilDto imageOfbase64UtilDto, List<YoutuPerson> youtuPersonList, Object orgId) {

        log.info("\n获取用户信息............ 开始..准备开始获取分布式锁......" + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{}", youtuPersonList.get(0).getUserId().toString());
        boolean lock = false;

        int retryCount = 0;
        while (!lock) {

            try {
                lock = redisTemplateUtil.tryLock(RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId(), youtuPersonList.get(0).getUserId().toString(), 120, TimeUnit.SECONDS);
                log.info("#################" + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{},加锁 ", youtuPersonList.get(0).getUserId().toString());

            } catch (Exception e) {
                log.info("#################加锁失败..等待锁过期 ：" + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{}", youtuPersonList.get(0).getUserId().toString());
                e.printStackTrace();

            }

            if (lock) {//加锁成功

                //判断当前用户在当前学校是否有注册人脸,如果没有人脸就注册person并且注册人脸,如果有一张就注册2张,如果有2张就不注册了
                log.info("---------准备注册人脸的学校ID和用户ID----------orgId:{},userId:{}", orgId, youtuPersonList.get(0).getUserId());
                String result = repiarAddUserFace(imageOfbase64UtilDto, null, UuIdUtil.getUserCodeByUUId(), Long.parseLong(String.valueOf(orgId)), youtuPersonList.get(0).getAccountId(), youtuPersonList.get(0).getUserId());

                log.info("---------打印人脸注册结果----------result:{}", result);
                try {
                    log.info("#################" + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{},释放锁 ", youtuPersonList.get(0).getUserId().toString());
                    redisTemplateUtil.releaseLock(RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId(), youtuPersonList.get(0).getUserId().toString());
                } catch (Exception e) {
                    log.info("#################释放锁失败..等待锁过期 ," + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{}", youtuPersonList.get(0).getUserId().toString());
                    e.printStackTrace();
                }
            } else {
                try {
                    retryCount++;
                    if(retryCount>20){
                        log.info("加锁失败，重试超过20次，注册人脸失败..." + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{}", youtuPersonList.get(0).getUserId().toString());
                        break;
                    }
                    log.info("等待500ms重试..." + RedisKeyConstant.WKBB_BASIC + "orgId:" + orgId + "userId:" + youtuPersonList.get(0).getUserId() + ":{}", youtuPersonList.get(0).getUserId().toString());
                    Thread.sleep(500L);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        }
    }


    @Override
    public void repairProYouTuInfo() {
        try {
            HashMap<String, Object> params = new HashMap<>(2);
            params.put("status", 0);
            List<YoutuFace> YoutuFaceList = youtuFaceMapper.getListFaceByStatus(params);
            log.info("---------获取所有status为0的人脸数据----------YoutuFaceList:{}", YoutuFaceList.size());

            if (YoutuFaceList.isEmpty()) {
                log.info("---------没查询到需要修复的数据----------");
                return;
            }

            for (YoutuFace youtuFace : YoutuFaceList) {
                params.put("personId", youtuFace.getPersonId());
                List<YoutuPerson> youtuPersonList = youtuPersonMapper.getPersonByStatus(params);

                if (!youtuPersonList.isEmpty()) {
                    params.clear();
                    params.put("personId", youtuFace.getPersonId());
                    YoutuPerson youtuPerson = youtuPersonMapper.getByMapParams(params);
                    List<HashMap> imagesList = new ArrayList<>();
//                    imagesList.add();
//                    HashMap imagesMap；
                    if (null == youtuPerson) {
                        addUserFaceByAccountId(FileUtil.batchEncodeImageToBase64(youtuFace.getWebUrl()), UuIdUtil.getUserCodeByUUId(), youtuPerson.getOrgId(), youtuPersonList.get(0).getAccountId(), youtuPersonList.get(0).getUserId());
                    } else {
                        List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);

                        if (youtuFaceList.size() == 1) {
                            addUserFaceByAccountId(FileUtil.batchEncodeImageToBase64(youtuFaceList.get(0).getWebUrl() + Constants.SEPARATOR_MARK + youtuFace.getWebUrl()), youtuPerson.getPersonId(), youtuPerson.getOrgId(), youtuPersonList.get(0).getAccountId(), youtuPersonList.get(0).getUserId());
                        }

                    }
                }
            }

        } catch (Exception e) {
            log.info("---------修复接口失败----------");
        }

    }


    public String addUserFaceByAccountId(List<ImageOfbase64UtilDto> imagesList, String userCode, Long orgId, Long accountId, Long userId) {
        ImageOfbase64UtilDto imageOfbase64UtilDto_a = null;
        ImageOfbase64UtilDto imageOfbase64UtilDto_b = null;
        if (imagesList.size() > 1) {
            //必须传2张图片
            imageOfbase64UtilDto_a = imagesList.get(0);
            imageOfbase64UtilDto_b = imagesList.get(1);
        }
        String result = null;
        log.info("---addUserFaceByAccountId--picUrla={},picUrlb={},userCode={},orgId={},accountId={},userId={}", imageOfbase64UtilDto_a.getImageUrl(), imageOfbase64UtilDto_b.getImageUrl(), userCode, orgId, accountId, userId);

        YoutuPerson youtuPerson = webankService.getYoutuPersonByParam(userCode);

        Boolean flag = true;
        if (null == youtuPerson) {

            result = repiaAddPerson(accountId, userCode, imageOfbase64UtilDto_a, accountId, userId);
            log.info("*************创建个体结束*************}", result);
            flag = false;

            //微众注册人员失败的话返回一个不是json的str
            if (!JSON.isValid(result)) {
                return result;
            }
        }
        if (null != result && YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode")) || null == result) {
            try {
                //对比照片是否同一个人
                if (StringUtil.isNotEmpty(imageOfbase64UtilDto_a.getImageUrl()) && StringUtil.isNotEmpty(imageOfbase64UtilDto_b.getImageUrl())) {
                    log.info("----对比照片是否同一个人----");
                    //人脸检测
                    result = getFaceDetect(imageOfbase64UtilDto_b);
                    if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode")) && Integer.parseInt(JSONObject.parseObject(result).get("face_num").toString()) > 0) {
                        //如果2个人脸不为空,2张图片进行对比,同一个人就上传B,不是同一个人就返回
                        result = getFaceCompare(imageOfbase64UtilDto_a, imageOfbase64UtilDto_b);
                        if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode")) && serviceConfig.getFaceCompare().compareTo(new BigDecimal(JSONObject.parseObject(result).get("result").toString())) < 1) {
                            //是同一個人上傳
                            List<ImageOfbase64UtilDto> imageOfbase64UtilDtoList = new ArrayList<ImageOfbase64UtilDto>();
                            imageOfbase64UtilDtoList.add(imageOfbase64UtilDto_a);
                            result = repiaAddFace(imageOfbase64UtilDtoList, userCode, orgId, userId);
                            return result;
                        }
                    }
                    return result;
                } else {
                    if (flag) {
                        log.info("----如果只有A脸,直接上传并返回结果----");
                        //如果只有A脸,直接上传并返回结果
                        result = getFaceDetect(imageOfbase64UtilDto_a);
                        if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode")) && Integer.parseInt(JSONObject.parseObject(result).get("face_num").toString()) > 0) {
                            List<ImageOfbase64UtilDto> imageOfbase64UtilDtoList = new ArrayList<ImageOfbase64UtilDto>();
                            imageOfbase64UtilDtoList.add(imageOfbase64UtilDto_a);
                            result = repiaAddFace(imageOfbase64UtilDtoList, userCode, orgId, userId);
                            return result;
                        }
                    }
                }
                log.info("*************人脸对比成功*************}", result);
            } catch (Exception e) {
                log.error("*************人脸对比失败*************}", e);
            }
        }
        return result;
    }

    //此接口修复完数据后可以删除
    public String repiarAddUserFace(ImageOfbase64UtilDto imageOfbase64UtilDto_a, ImageOfbase64UtilDto imageOfbase64UtilDto_b, String userCode, Long orgId, Long accountId, Long userId) {
        String result = null;
        log.info("---repiarAddUserFace--picUrla={},picUrlb={},userCode={},orgId={},accountId={},userId={}", imageOfbase64UtilDto_a.getImageUrl(), imageOfbase64UtilDto_b.getImageUrl(), userCode, orgId, accountId, userId);


        //通过orgId,userId获取个体是否创建
        YoutuPerson youtuPerson = getYoutuPerson(orgId, userId);

        log.info("----------当前用户YouTuPerson对象----------youtuPerson:{}", youtuPerson);
        if (null == youtuPerson) {
            //创建个体
            log.info("*************开始创建个体*************}");

            //生成userCode
            userCode = UuIdUtil.getUserCodeByUUId();
            log.info("--------创建个体最新生成的userCode---------,userCode={}", userCode);

            result = repiaAddPerson(orgId, userCode, imageOfbase64UtilDto_a, accountId, userId);
            log.info("*************创建个体结束*************result:{}", result);
            return result;
        } else {
            userCode = youtuPerson.getPersonId();
        }

        HashMap<String, Object> params = new HashMap<>(2);
        params.put("personId", userCode);
        List<YoutuFace> youtuFaceList = youtuFaceMapper.getListByMapParams(params);

        log.info("--------查询当前用户已有人脸个数---------,youtuFaceList={}", youtuFaceList);
        if (youtuFaceList.size() == 1) {

            log.info("--------当前用户只有一张人脸,注册第二张---------,youtuFaceList={}", youtuFaceList);
            List<ImageOfbase64UtilDto> imageOfbase64UtilDtoList = new ArrayList<ImageOfbase64UtilDto>();
            imageOfbase64UtilDtoList.add(imageOfbase64UtilDto_a);
            result = repiaAddFace(imageOfbase64UtilDtoList, userCode, orgId, userId);
        } else {
            log.info("--------当前用户已有2张人脸---------,orgId={},userId={}", orgId, userId);
        }
        return result;
    }

    //此接口修复完数据后可以删除
    public String repiaAddPerson(Long orgId, String personId, ImageOfbase64UtilDto imageOfbase64UtilDto, Long accountId, Long userId) {
        String result = null;

        JSONObject jsonObject = new JSONObject();
        try {

            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            //group_ids进行补位
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), orgId.toString());
            List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
//            String image = FileUtil.encodeImageToBase64(new URL(picUrl));

            jsonObject.put("group_ids", accountList);
            jsonObject.put("person_id", personId);
            jsonObject.put("image", imageOfbase64UtilDto.getBase64());

            log.info("----------创建个体对象---------url:{},JsonObject:{},sign:{},token:{}", basicConfig.getUtuUrl() + YouTuUtil.ADDPERSON, JSON.toJSONString(jsonObject), sign, basicConfig.getUtuTxToken());
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.ADDPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

            log.info("*****创建个体对象结果******result:{}", JSONObject.parseObject(result));
            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                JSONObject jsonObject1 = JSONObject.parseObject(result);
                String faceId = jsonObject1.get("face_id").toString();

                YoutuPerson youtuPerson = new YoutuPerson();
                youtuPerson.setAccountId(accountId);
                youtuPerson.setUserId(userId);
                youtuPerson.setOrgId(orgId);
                youtuPerson.setPersonId(personId);
                youtuPerson.setStatus(true);
                youtuPersonMapper.insert(youtuPerson);

                YoutuFace youtuFace = new YoutuFace();
                youtuFace.setPersonId(personId);
                youtuFace.setFaceId(faceId);
                youtuFace.setWebUrl(imageOfbase64UtilDto.getImageUrl());
                youtuFace.setFaceType(FaceTypeEnum.JUSTFACE.getValue().byteValue());
                youtuFace.setSourceType(YouTuUtil.SOURCETYPE);
                youtuFace.setYouTuStatus(true);
                youtuFaceMapper.insert(youtuFace);
                log.info("个体创建成功JsonObject-{}",JSONObject.toJSONString(youtuFace));
            }
        } catch (Exception e) {
            //同时删除微众人脸
            log.error("个体创建失败e-{}", e.getMessage());
        }
        return result;
    }

    //此接口修复完数据后可以删除
    //为了减少encodeImageToBase64使用次数，这里只能把picUrl和encodeImageToBase64之后的结果一起传进来
    public String repiaAddFace(List<ImageOfbase64UtilDto> imagesList, String personId, Long orgId, Long userId) {

        String result = null;
        JSONObject jsonObject = new JSONObject();
        //获取签名
        try {

            List base64List = new ArrayList();
            List picUrlList = new ArrayList();
            for (ImageOfbase64UtilDto imageOfbase64UtilDto : imagesList) {
                base64List.add(imageOfbase64UtilDto.getBase64());
                picUrlList.add(imageOfbase64UtilDto.getImageUrl());
            }

            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            jsonObject.put("person_id", personId);

            jsonObject.put("images", base64List);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.ADDFACE, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            JSONObject jsonObjectResult = JSONObject.parseObject(result);

            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode")) && new BigDecimal(JSONObject.parseObject(result).get("added").toString()).compareTo(new BigDecimal(0)) == 1) {
                JSONArray jsonArray = jsonObjectResult.getJSONArray("face_ids");
                int i = 0;
                if (null != jsonArray && jsonArray.size() > 0) {
                    for (int j = 0; j < jsonArray.size(); j++) {
                        Object faceId = jsonArray.get(j);
                        YoutuFace youtuFace = new YoutuFace();
                        youtuFace.setPersonId(personId);
                        youtuFace.setFaceId(faceId.toString());
                        youtuFace.setWebUrl(picUrlList.get(i).toString());
                        youtuFace.setFaceType(FaceTypeEnum.JUSTFACE.getValue().byteValue());
                        youtuFace.setSourceType(YouTuUtil.SOURCETYPE);
                        youtuFace.setYouTuStatus(true);
                        youtuFaceMapper.insert(youtuFace);

                    }
                }
                log.info("人脸添加成功");
            }
        } catch (Exception e) {
            log.error("人脸添加失败", e);
        }

        return result;
    }

    @Override
    public void repairWeBankFace(Long orgId) {

        try {

            log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
            OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);
            log.info("--------获取学校微众appid结束--------orgId:{}", orgId);

            HashMap<String, Object> params = new HashMap<>(2);
            params.put("status", 0);
            List<YoutuFace> YoutuFaceList = youtuFaceMapper.getListFaceByStatus(params);

            log.info("---------删除所有face表status为0的微众人脸数据----------YoutuFaceList:{}", YoutuFaceList.size());
            if (YoutuFaceList.isEmpty()) {
                log.info("---------YoutuFaceList数据为空----------");
                return;
            }

            for (YoutuFace youtuFace : YoutuFaceList) {
                log.info("-------准备删除微众人脸--------");
                //在微众删除相应人员
                String webankResult = webankUtilService.delPerson(youtuFace.getPersonId(), false, organizationWebank.getWebankAppid(), organizationWebank.getWebankSecret(), orgId);
                //删除微众人脸的时候，若用户不存在，不予理会，不妨碍优图逻辑
                if ((!WebankUtil.userNotExists(webankResult))) {
                    //微众人脸删除失败，抛出异常终止人脸删除
                    if (!WebankUtil.checkIfSuccess(webankResult)) {
                        log.error("删除微众人脸失败:{}", webankResult);

                    }
                }
            }

        } catch (Exception e) {
            log.error("-------删除微众人脸异常--------", e);
        }
    }

    @Override
    public void repairDeleteBoxPerson() {

        try {

            HashMap<String, Object> params = new HashMap<>(2);
            params.put("status", 0);
            List<YoutuFace> YoutuFaceList = youtuFaceMapper.getListFaceByStatus(params);

            log.info("---------删除所有face表status为0的巨龙人员数据----------YoutuFaceList:{}", YoutuFaceList.size());
            if (YoutuFaceList.isEmpty()) {
                log.info("---------YoutuFaceList数据为空----------");
                return;
            }

            for (YoutuFace youtuFace : YoutuFaceList) {
                YoutuPerson youtuPerson = webankService.getYoutuPersonByParam(youtuFace.getPersonId());
                if(null!=youtuPerson){

                    //在巨龙盒子删除相应人员
                    log.info("---------准备删除巨龙相应人员----------personId:{}", youtuFace.getPersonId());
                    deviceBoxService.deleteBoxPerson(youtuFace.getPersonId(),youtuPerson.getOrgId());
                    log.info("---------删除巨龙相应人员结束----------personId:{}", youtuFace.getPersonId());
                }
            }

        } catch (Exception e) {
            log.error("-------删除巨龙人员异常--------", e);
        }
    }


    @Override
    public String changeUrl(String url) {
        try {
            if (isChangeUrl(url)) {
                //通过网络流的方式上传图片到cos
                ResultDTO<COSCredentialDto> resultDTO = tcCloudFeignService.getCredential();
                if (ResultDTO.checkSuccess(resultDTO) && resultDTO.getData() != null) {

                    ResultDTO<Object> picUrlResult = tcCloudFeignService.getPicUrl(resultDTO.getData().getCredentials().getTmpSecretId(), resultDTO.getData().getCredentials().getTmpSecretKey(), resultDTO.getData().getCredentials().getSessionToken(), CosFileTypeEnum.FACETYPE.getValue(), CountTypeEnum.IMGTYPE.getValue(), url);
                    Thread.sleep(600);

                    if (ResultDTO.checkSuccess(picUrlResult) && picUrlResult.getData() != null) {
                        log.info("----------打印cos地址---------url:{}", picUrlResult.getData());
                        url = picUrlResult.getData().toString();
                    }
                }

            }

        } catch (Exception e) {
            log.error("-----------替换URL异常----------", e);
        }
        return url;
    }

    public Boolean isChangeUrl(String url) {
        //因上传人脸基类接口增加缩略图后缀,所有人脸迁移地址都需要替换成COS地址
        if (url.contains(YouTuUtil.COSLINKPRO) || url.contains(YouTuUtil.COSLINKSMART) || url.contains(YouTuUtil.COSLINKWX) || url.contains(YouTuUtil.COSLINKWXTEST)) {
            return false;
        }
        return true;
    }

    @Override
    public List<YoutuPerson> youtuPersonList(Map<String, Object> params) {
        return youtuPersonMapper.getListByMapParams(params);
    }

    @Override
    public void deleteOldPerson(String accountId) {

        String result = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            String groupIds = UuIdUtil.getGroupIds(serviceConfig.getProfilesActive(), accountId);
            jsonObject.put("group_id", groupIds);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.PULLPERSONS, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

            String person_list = JSONObject.parseObject(result).get("person_list").toString();

            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                JSONArray jsonArray = JSONObject.parseArray(person_list);

                if (null != jsonArray && jsonArray.size() > 0) {
                    for (int i = 0; i < jsonArray.size(); i++) {
                        String personId = jsonArray.getJSONObject(i).getString("person_id");

                        jsonObject.put("person_id", personId);
                        result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

                        log.info("个体删除成功JsonObject-{}", result);
                    }
                }

            }
        } catch (Exception e) {
            log.info("个体删除异常JsonObject-{}", e);

        }
    }

    @Override
    public void repiarFaceLink(String url) {

        HashMap<String, Object> params = new HashMap<>();
        params.put("webUrl", url);

        List<YoutuFace> youTuFaceList = youtuFaceMapper.getListByMapParams(params);
        log.info("----------获取当前路径所有人脸数量----------youTuFaceList:{}", youTuFaceList.size());
        int size = youTuFaceList.size();
        if (CollectionUtils.isNotEmpty(youTuFaceList)) {
            for (YoutuFace youtuFace : youTuFaceList) {
                log.info("---------还剩下多少数据量未执行----------YoutuFaceList:{}", --size);
                String changeUrl = changeUrl(youtuFace.getWebUrl());
                youtuFace.setWebUrl(changeUrl);
                youtuFaceMapper.update(youtuFace);
            }
        }
    }


    @Override
    public String deletePersonBypersonId(Long orgId, String personIds, String profilesActive) {

        log.info("----------查询personIds------personIds:{}", personIds);
        String result = null;
        List personIdList = Arrays.asList(personIds.split(Constants.SEPARATOR_MARK));
        log.info("--------开始查询学校微众appid--------orgId:{}", orgId);
        OrganizationWebank organizationWebank = organizationWebankService.getOrganizationWebanksByOrgId(orgId, null);
        log.info("--------获取学校微众appid结束--------orgId:{}", orgId);

        if (null == organizationWebank) {
            log.info("--------此学校没有绑定微众appid--------orgId:{}", orgId);
            return null;
        }

        try {
            if (CollectionUtils.isNotEmpty(personIdList)) {
                for (Object personIdObject : personIdList) {
                    String personId = String.valueOf(personIdObject);
                    JSONObject jsonObject = new JSONObject();

                    //在微众删除相应人员
                    String webankResult = webankUtilService.delPerson(personId, false, organizationWebank.getWebankAppid(), organizationWebank.getWebankSecret(), orgId);
                    //删除微众人脸的时候，若用户不存在，不予理会，不妨碍优图逻辑
                    if ((!WebankUtil.userNotExists(webankResult))) {
                        //微众人脸删除失败，抛出异常终止人脸删除
                        if (!WebankUtil.checkIfSuccess(webankResult)) {
                            log.error("删除微众人员失败:{}", webankResult);
                            return WebankUtil.getMessage(webankResult);
                        }
                    }

                    //获取签名
                    String sign = geYouTuSign();
                    jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
                    jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
                    //group_ids进行补位
                    String groupIds = UuIdUtil.getGroupIds(profilesActive, orgId.toString());
                    List accountList = Arrays.asList(groupIds.split(Constants.SEPARATOR_MARK));
                    jsonObject.put("group_ids", accountList);
                    jsonObject.put("person_id", personId);
                    result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.DELETEPERSON, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());

                    if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                        Map<String, Object> params = new HashMap<>(1);
                        params.put("personId", personId);
                        if (null != personId) {
                            //在巨龙盒子删除相应人员
                            deviceBoxService.deleteBoxPerson(personId,orgId);

                            //通过userCode获取用户信息
                            Map<String, Object> param = new HashMap<>(1);
                            param.put("userCode", personId);

                            User user = userService.getByMapParams(param);

                            if (null != user) {
                                ThreadPoolUtil.addPoolTask(new SynUserAccessXmppTask(doorFeignService, orgId, user.getId(), RoleTypeEnum.FAMILY, xmppService, null, null, null, true, false, false, false,null,null));
                            }
                        }
                    }
                    log.info("----------个体删除成功----------JsonObject:{}", jsonObject);
                }
            }
        } catch (Exception e) {
            log.info("----------个体删除失败----------", e);
        }
        return result;
    }


    @Override
    public String comparePersonId(Long orgId, String profilesActive) {

        String result = null;
        String personIds = null;
        JSONObject jsonObject = new JSONObject();
        try {
            //获取签名
            String sign = geYouTuSign();
            jsonObject.put("app_id", basicConfig.getUtuSdkAppid().toString());
            jsonObject.put("session_id", UuIdUtil.getSessionIdByUUId());
            String groupIds = UuIdUtil.getGroupIds(profilesActive, orgId.toString());

            jsonObject.put("group_id", groupIds);
            result = YouTuUtil.post(basicConfig.getUtuUrl() + YouTuUtil.PULLPERSONS, JSON.toJSONString(jsonObject), "UTF-8", sign, basicConfig.getUtuTxToken());
            String person_list = JSONObject.parseObject(result).get("person_list").toString();

            if (YouTuUtil.ERRORCODETYPE.equals(JSONObject.parseObject(result).get("errorcode"))) {
                JSONArray jsonArray = JSONObject.parseArray(person_list);

                if (null != jsonArray && jsonArray.size() > 0) {
                    for (int i = 0; i < jsonArray.size(); i++) {
                        Boolean flag = true;
                        String personId = jsonArray.getJSONObject(i).getString("person_id");

                        Map<String, Object> params = new HashMap<>(2);
                        params.put("orgId", orgId);
                        List<YoutuPerson> youtuPersonList = youtuPersonMapper.getListByMapParams(params);

                        for (YoutuPerson youtuPerson : youtuPersonList) {
                            if (personId.equals(youtuPerson.getPersonId())) {
                                flag = false;
                            }
                        }

                        if (flag) {
                            if (StringUtil.isEmptyIgnoreBlank(personIds)) {
                                personIds = personId;
                            } else {
                                personIds = personIds + ";" + personId;
                            }
                        }
                    }
                }
            }
        } catch (Exception e) {
            log.info("个体删除异常JsonObject-{}", e);
        }
        return personIds;
    }


    private void CheckYouTuFace(String personId, Boolean flag, String faceId) {
        Map<String, Object> params = new HashMap<>();
        params.put("personId", personId);

        //通过userCode获取个体是否创建
        List<YoutuFace> YoutuFaceList = youtuFaceMapper.getListByMapParams(params);

        if (CollectionUtils.isNotEmpty(YoutuFaceList)) {

            for (YoutuFace youtuFace : YoutuFaceList) {

                if (StringUtil.isNotEmptyIgnoreBlank(faceId)) {

                    youtuFace.setFaceId(faceId);
                }
                if (flag) {
                    youtuFace.setYouTuStatus(flag);
                } else {
                    youtuFace.setYouTuStatus(false);
                }
                youtuFaceMapper.update(youtuFace);
                log.info("个体创建成功JsonObject-{}");
            }
        }
    }

    /**
     * 查询机构下的用户人脸列表
     * @param orgId
     * @param userId
     * @return
     */
//    @Override
//    public List<DeviceUserFaceVo>  getFaceListByOrgAndUser(Long orgId,Long userId){
//        if(orgId==null && userId==null){
//            return null;//不允许查全表
//        }
//        HashMap<String, Object> params = new HashMap<>();
//        params.put("orgId", orgId);
//        params.put("userId", userId);
////        return   youtuFaceMapper.getFaceListByOrgAndUser(params);
//        return null;
//    }

}